#pragma once
// 防止头文件重复包含
#include "Common.hpp"
#include "ThreadCache.hpp"
#include "CentralCache.hpp"
#include "PageCache.hpp"
#include "ObjectPool.hpp"
// static 设置函数为静态函数 避免跨翻译单元的符号冲突
// 同一个函数在每个翻译单元里互不可见
// TurboAlloc 对比 malloc
// TurboFree 对比 free
static void *TurboAlloc(size_t size)
{
    if (size > MAX_BYTES)
    {
        size_t alignSize = SizeClass::RoundUp(size); // 根据size内存对齐后获得alignSize
        size_t kpage = alignSize >> PAGE_SHIFT;      // 需要多少页
        PageCache::GetInstance()->_pageMtx.lock();
        Span *span = PageCache::GetInstance()->NewSpan(kpage);
        span->_objSize = size;
        PageCache::GetInstance()->_pageMtx.unlock();
        void *ptr = (void *)(span->_pageId << PAGE_SHIFT);
        return ptr;
    }
    else
    {
        // 通过TLS 每个线程无锁的获取属于自己的专属ThreadCache对象
        //  pTLSThreadCache是一个ThreadCache指针
        if (pTLSThreadCache == nullptr)
        {
            static ObjectPool<ThreadCache> tcPool;
            pTLSThreadCache = tcPool.New();
            // 通过ObjectPool 管理TLSThreadCache的资源
        }
        // return nullptr;
        return pTLSThreadCache->Allocate(size);
    }
}
static void TurboFree(void *ptr)
{
    Span*span=PageCache::GetInstance()->MapObjectToSpan(ptr);
    size_t size=span->_objSize;
    if(size>MAX_BYTES)
    {
        PageCache::GetInstance()->_pageMtx.lock();
        PageCache::GetInstance()->ReleaseSpanToPageCache(span);
        PageCache::GetInstance()->_pageMtx.unlock();
    }
    else
    {
        assert(pTLSThreadCache);
        pTLSThreadCache->Deallocate(ptr,size);
    }
}